package com.example.dangerouscargodriver.controller;

import android.content.Context;
import android.os.Message;
import android.util.Log;

import com.baiju.netmanager.Http.HttpRequest;
import com.baiju.netmanager.Http.IHttpRequest;
import com.baiju.netmanager.Http.INetResponse;
import com.example.dangerouscargodriver.DangerousCargoDriverApplication;
import com.example.dangerouscargodriver.entry.CompanyInfo;
import com.example.dangerouscargodriver.entry.CompanyMainInfo;
import com.example.dangerouscargodriver.entry.EnterStatus;
import com.example.dangerouscargodriver.entry.TruckDetailInfo;
import com.example.dangerouscargodriver.entry.UserInfo;
import com.example.dangerouscargodriver.event.Event;
import com.example.dangerouscargodriver.event.LoadHttpResourceStatus;
import com.example.dangerouscargodriver.module.ResponseInfo;
import com.example.dangerouscargodriver.param.RemoteAPI;
import com.example.dangerouscargodriver.param.RemoteAPICmd;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.lang.reflect.Type;
import java.util.HashMap;
import java.util.List;

public class EnterPlatformInfoController extends Controller{

    private static final String TAG = "EnterPlatformController";
    private static EnterPlatformInfoController mInstance = null;

    public static final int ENTER_STATUS_NONE = 0;
    public static final int ENTER_STATUS_PERSONAL = 1;
    public static final int ENTER_STATUS_COMPANY = 2;
    public static final int ENTER_STATUS_NULL = 4;

    public static final int LOAD_ENTER_STATUS_DOING = 0;
    public static final int LOAD_ENTER_STATUS_DONE = 1;

    private static final int MSG_ADD_LISTENER = 0;
    private static final int MSG_ENTER_STATUS_LOAD = 2;
    private static final int MSG_LOAD_COMPANY_INFO = 3;
    private static final int MSG_LOAD_COMPANY_INFO_DONE = 4;
    private static final int MSG_LOAD_PERSONAL_TRUCK_INFO = 5;
    private static final int MSG_LOAD_PERSONAL_TRUCK_INFO_DONE = 6;
    private static final int MSG_UPDATE_ENTER_STATUS = 7;

    private HttpRequest mHttp = null;
    private HttpResponseListener mHttpListener = null;

    private HashMap<Class, IControllerEventListener> mControllerListener = null;

    private List<CompanyInfo> mCompanyInfoList = null;

    private TruckDetailInfo mTruckDetailInfo = null;

    private int mEnterStatus = ENTER_STATUS_NULL;

    private int mLoadEnterStatus = LOAD_ENTER_STATUS_DOING;

    private String mPersonalTid = null;

    private UserInfo mUserInfo = null;

    public static EnterPlatformInfoController Instance(){
        if(mInstance == null){
            mInstance = new EnterPlatformInfoController(DangerousCargoDriverApplication.getAppContext());
        }

        return mInstance;
    }

    public EnterPlatformInfoController(Context context){
        mHttpListener = new HttpResponseListener();
        mControllerListener = new HashMap<>();
        mHttp = HttpRequest.Instance(context);
        mHttp.attachResponseListener(mHttpListener, EnterPlatformInfoController.class);
        mHttp.startUp();

        mLoadEnterStatus = LOAD_ENTER_STATUS_DOING;
        mUserInfo = UserInfoController.Instance().getUserInfo();
        if(mUserInfo != null) {
            if(mUserInfo.getRole() == 1){
                mEnterStatus = ENTER_STATUS_NONE;
            }
            else if(mUserInfo.getRole() == 2){
                mEnterStatus = ENTER_STATUS_COMPANY;
                executeSearchCompanyInfo();
            }
            else if(mUserInfo.getRole() == 3){
                mEnterStatus = ENTER_STATUS_PERSONAL;
                executeSettleCheck();
            }
            else{
                mEnterStatus = ENTER_STATUS_NULL;
            }
        }
    }

    public boolean attachControllerListener(Class object, IControllerEventListener listener){
        if(mControllerListener.containsKey(object)){
            return false;
        }
        else {
            mControllerListener.put(object, listener);
            Message msg = new Message();
            msg.what = MSG_ADD_LISTENER;
            msg.obj = object;
            sendMessage(msg);

            return true;
        }
    }

    public boolean unAttachControllerListener(Class object, IControllerEventListener listener){
        if(mControllerListener.containsKey(object) && mControllerListener.get(object) == listener){
            mControllerListener.remove(object);
            return true;
        }
        else {
            return false;
        }
    }

    public void updateEnterStatus(){
        mLoadEnterStatus = LOAD_ENTER_STATUS_DOING;
        mUserInfo = UserInfoController.Instance().getUserInfo();
        if(mUserInfo != null) {
            if(mUserInfo.getRole() == 1){
                mEnterStatus = ENTER_STATUS_NONE;
            }
            else if(mUserInfo.getRole() == 2){
                mEnterStatus = ENTER_STATUS_COMPANY;
                executeSearchCompanyInfo();
            }
            else if(mUserInfo.getRole() == 3){
                mEnterStatus = ENTER_STATUS_PERSONAL;
                executeSettleCheck();
            }
            else{
                mEnterStatus = ENTER_STATUS_NULL;
            }
        }
        else{
            Message message = new Message();
            message.what = MSG_UPDATE_ENTER_STATUS;
            sendMessageDelayed(message, 1000);
        }
    }

    public int getTid(){
        if(mPersonalTid != null){
            return Integer.parseInt(mPersonalTid);
        }
        else{
            return -1;
        }
    }

    public int getEnterStatus(){
        return mEnterStatus;
    }

    public List<CompanyInfo> getCompanyInfoList(){
        return mCompanyInfoList;
    }

    private void executeSearchCompanyInfo(){
        HashMap<String, String> header = new HashMap<String, String>();
        header.put("token", AuthController.Instance().getToken());
        header.put("app-type", "Android");

        mHttp.sendRequest(
                IHttpRequest.RequestMethod.GET_METHOD,
                RemoteAPI.REQUEST_V1_USER_COMPANY,
                header,
                null,
                RemoteAPICmd.REQUEST_V1_USER_COMPANY,
                EnterPlatformInfoController.class);
    }

    private void executeSearchPersonalTruckInfo(){
        HashMap<String, String> header = new HashMap<String, String>();
        header.put("token", AuthController.Instance().getToken());

        if(mPersonalTid != null) {
            mHttp.sendRequest(
                    IHttpRequest.RequestMethod.GET_METHOD,
                    RemoteAPI.REQUEST_V1_USER_REGISTER_TRUCK + "/" + mPersonalTid,
                    header,
                    null,
                    RemoteAPICmd.REQUEST_V1_USER_REGISTER_TRUCK,
                    EnterPlatformInfoController.class);
        }
        else{
            /**/
        }
    }

    private void executeSettleCheck(){
        HashMap<String, String> header = new HashMap<String, String>();
        header.put("token", AuthController.Instance().getToken());

        mHttp.sendRequest(
                IHttpRequest.RequestMethod.GET_METHOD,
                RemoteAPI.REQUEST_V1_USER_SETTLE_BEFORE_CHECK,
                header,
                null,
                RemoteAPICmd.REQUEST_V1_USER_SETTLE_BEFORE_CHECK,
                EnterPlatformInfoController.class);
    }

    @Override
    public void handleControllerMessage(Message msg){
        switch (msg.what){
            case MSG_UPDATE_ENTER_STATUS:
                updateEnterStatus();
                break;
            case MSG_ADD_LISTENER:
                LoadHttpResourceStatus status = new LoadHttpResourceStatus();
                status.setWhat(mLoadEnterStatus);
                mControllerListener.get(msg.obj).onEvent(Event.EVENT_LOAD_HTTP_ENTER_STATUS, status.toJson());
                break;
            case MSG_ENTER_STATUS_LOAD:
                executeSettleCheck();
                break;
            case MSG_LOAD_COMPANY_INFO:
                executeSearchCompanyInfo();
                break;
            case MSG_LOAD_PERSONAL_TRUCK_INFO:
                executeSearchPersonalTruckInfo();
                break;
            case MSG_LOAD_COMPANY_INFO_DONE:
            case MSG_LOAD_PERSONAL_TRUCK_INFO_DONE:
                mLoadEnterStatus = LOAD_ENTER_STATUS_DONE;
                for (Class key : mControllerListener.keySet()) {
                    LoadHttpResourceStatus loadHttpResourceStatus = new LoadHttpResourceStatus();
                    loadHttpResourceStatus.setWhat(mLoadEnterStatus);
                    mControllerListener.get(key).onEvent(Event.EVENT_LOAD_HTTP_ENTER_STATUS,
                            loadHttpResourceStatus.toJson());
                }
                break;
            default:
                break;
        }
    }

    private class HttpResponseListener implements INetResponse {

        @Override
        public void onResponse(int actionId, String response) {
            try {
                JSONObject res = new JSONObject(response);
                Gson gson = new Gson();
                if(actionId == RemoteAPICmd.REQUEST_V1_USER_COMPANY){
                    Log.d(TAG, "onResponse: " + response);
                    ResponseInfo responseInfo = gson.fromJson(response, ResponseInfo.class);
                    if(responseInfo != null && responseInfo.getStatus() == 1){
                        JSONArray data = res.getJSONArray("data");
                        Type type = new TypeToken<List<CompanyInfo>>() {}.getType();
                        mCompanyInfoList = gson.fromJson(data.toString(), type);
                        if(mCompanyInfoList != null && mCompanyInfoList.size() > 0){
                            Message message = new Message();
                            message.what = MSG_LOAD_COMPANY_INFO_DONE;
                            sendMessage(message);
                        }
                        else{
                            /**/
                        }
                    }
                    else{
                        Message message = new Message();
                        message.what = MSG_LOAD_COMPANY_INFO;
                        sendMessageDelayed(message, 1000);
                    }
                }
                else if(actionId == RemoteAPICmd.REQUEST_V1_USER_SETTLE_BEFORE_CHECK){
                    Log.d(TAG, "onResponse: " + response);
                    ResponseInfo responseInfo = gson.fromJson(response, ResponseInfo.class);
                    if(responseInfo != null && responseInfo.getStatus() == 50001){
                        mPersonalTid = res.getJSONObject("data").getString("tid");
                        executeSearchPersonalTruckInfo();
                    }
                    else{
                        /**/
                    }
                }
                else if(actionId == RemoteAPICmd.REQUEST_V1_USER_REGISTER_TRUCK){
                    Log.d(TAG, "onResponse: " + response);
                    ResponseInfo responseInfo = gson.fromJson(response, ResponseInfo.class);
                    if(responseInfo != null && responseInfo.getStatus() == 1){
                        mTruckDetailInfo = gson.fromJson(res.getString("data"), TruckDetailInfo.class);
                        Message message = new Message();
                        message.what = MSG_LOAD_PERSONAL_TRUCK_INFO_DONE;
                        sendMessageDelayed(message, 1000);
                    }
                    else{
                        Message message = new Message();
                        message.what = MSG_LOAD_PERSONAL_TRUCK_INFO;
                        sendMessageDelayed(message, 1000);
                    }
                }
                else{

                }
            }
            catch (JSONException e) {
                e.printStackTrace();
            }
        }

        @Override
        public void onErrorResponse(int actionId, String response) {
            if(actionId == RemoteAPICmd.REQUEST_V1_USER_COMPANY){
                Message message = new Message();
                message.what = MSG_LOAD_COMPANY_INFO;
                sendMessageDelayed(message, 1000);
            }
            else if(actionId == RemoteAPICmd.REQUEST_V1_USER_REGISTER_TRUCK){
                Message message = new Message();
                message.what = MSG_LOAD_PERSONAL_TRUCK_INFO;
                sendMessageDelayed(message, 1000);
            }
            else if(actionId == RemoteAPICmd.REQUEST_V1_PLACE_ORDER_CHECK){
                Message message = new Message();
                message.what = MSG_ENTER_STATUS_LOAD;
                sendMessageDelayed(message, 1000);
            }
        }
    }
}
